Using MkDocs

mkdocs
documentation
static-site
python
Using MkDocs with GitHub Pages for Documentation
Author

Dario Airoldi

Published

December 16, 2025

Modified

December 29, 2025

Using MkDocs with GitHub Pages for Documentation

📋 Table of Contents

📖 Overview

MkDocs is a fast, simple, and elegant static site generator specifically designed for building project documentation. Written in Python, it takes Markdown source files and converts them into a professional static HTML documentation website.

Key characteristics of MkDocs:

  • Python-based: Built with Python, leveraging the powerful Python-Markdown library
  • Simplicity-first: Single YAML configuration file (mkdocs.yml)
  • Fast builds: Optimized for quick documentation generation
  • Live preview: Built-in development server with auto-reload
  • Theme support: Multiple built-in and community themes available
  • Plugin ecosystem: Extensible through a rich plugin architecture

💡 Key Concepts

1. Project Structure

MkDocs follows a straightforward project structure that’s easy to understand and maintain.

Minimal Project Structure

The simplest MkDocs project contains just two elements:

my-project/
├── mkdocs.yml       # Configuration file
└── docs/            # Documentation source files
    └── index.md     # Homepage

Standard Documentation Structure

A typical MkDocs documentation project follows this structure:

your-repo/
├── mkdocs.yml           # MkDocs configuration file
├── docs/                # Source markdown files
│   ├── index.md         # Homepage
│   ├── getting-started.md
│   ├── user-guide/
│   │   ├── index.md
│   │   ├── installation.md
│   │   └── configuration.md
│   ├── reference/
│   │   ├── index.md
│   │   └── api.md
│   └── img/             # Images and media
│       └── screenshot.png
├── site/                # Generated output (after build)
├── custom_theme/        # Custom theme files (optional)
└── .github/
    └── workflows/
        └── deploy.yml   # CI/CD workflow

Learn Repository Structure Example

For a repository like a “Learn” repo with existing folder structure, you could adapt it as follows:

Learn/                              # Your existing repository
├── mkdocs.yml                      # MkDocs configuration
├── docs/                           # Documentation root
│   ├── index.md                    # Main landing page
│   ├── events/
│   │   ├── index.md                # Events overview
│   │   └── build-2025/
│   │       ├── index.md            # Build 2025 overview
│   │       └── sessions/           # Session notes
│   ├── azure/                      # Azure topics
│   │   ├── index.md
│   │   ├── naming-conventions.md
│   │   └── storage-access.md
│   └── tools/                      # Development tools
│       ├── index.md
│       ├── git-cli.md
│       └── http-testing.md
└── site/                           # Generated output

2. Configuration File (mkdocs.yml)

The mkdocs.yml file is the heart of your MkDocs project configuration. Only the site_name setting is required.

Minimal Configuration

site_name: My Documentation

Standard Configuration

site_name: Your Documentation
site_url: https://example.com/docs/
site_author: Your Name
site_description: A brief description of your documentation

repo_url: https://github.com/username/repository
repo_name: GitHub

nav:
  - Home: index.md
  - Getting Started: getting-started.md
  - User Guide:
    - Installation: user-guide/installation.md
    - Configuration: user-guide/configuration.md
  - Reference:
    - API: reference/api.md

theme:
  name: material  # or 'mkdocs', 'readthedocs'
  locale: en

plugins:
  - search

markdown_extensions:
  - toc:
      permalink: true
  - admonition
  - codehilite

extra_css:
  - css/custom.css

extra_javascript:
  - js/custom.js

Key Configuration Options

Option Description Default
site_name Required. Main title for the documentation -
site_url Canonical URL of the site null
repo_url URL to the source repository null
nav Navigation structure Auto-generated
theme Theme configuration mkdocs
plugins List of enabled plugins ['search']
docs_dir Source directory docs
site_dir Output directory site

Configuration Inheritance

MkDocs supports configuration inheritance using the INHERIT key, allowing multiple sites to share common configuration:

# base.yml - shared configuration
theme:
  name: material
  locale: en

markdown_extensions:
  toc:
    permalink: true
  admonition: {}
# mkdocs.yml - project-specific configuration
INHERI: ../base.yml
site_name: My Project
site_url: https://example.com/my-project

Deep merging allows you to add or override values while retaining parent configuration. This is particularly useful for organizations maintaining multiple documentation sites.

Special YAML Tags

MkDocs supports special YAML tags for dynamic configuration:

Environment Variables (!ENV):

site_name: !ENV [SITE_NAME, 'My Default Site']
plugins:
  - search
  - code-validator:
      enabled: !ENV [LINT, false]

Relative Paths (!relative):

markdown_extensions:
  - pymdownx.snippets:
      base_path: !relative  # Relative to current Markdown file

3. Source Directory (docs/)

  • Purpose: Contains your source Markdown (.md) files
  • Default location: docs/ relative to mkdocs.yml
  • Best Practices:
    • Use clear, descriptive filenames
    • Organize content hierarchically with subdirectories
    • Include an index.md as your homepage
    • Use YAML front matter for page metadata

Index Pages

MkDocs supports two conventions for index pages:

  1. index.md - Standard index file
  2. README.md - Repository-friendly alternative (rendered as index.html)

If both exist in the same directory, index.md takes precedence.

4. Output Directory (site/)

  • Purpose: Contains the generated HTML files after running mkdocs build
  • Default location: site/ relative to mkdocs.yml
  • Important Notes:
    • Generated automatically by MkDocs
    • Should typically be added to .gitignore
    • Contains all HTML, CSS, JS, and assets for deployment

5. Document Management (MkDocs 1.5+)

MkDocs provides powerful options for managing which documents are included in your site:

Excluding Documents (exclude_docs)

Exclude files from the built site using .gitignore-style patterns:

exclude_docs: |
  api-config.json    # A file with this name anywhere
  /requirements.txt  # Top-level "docs/requirements.txt"
  *.py               # Any file with this extension
  !/foo/example.py   # But keep this particular file

Draft Documents (draft_docs) - MkDocs 1.6+

Mark documents as drafts - available during mkdocs serve but excluded from builds:

draft_docs: |
  drafts/               # A "drafts" directory anywhere
  _unpublished.md       # Files ending in _unpublished.md

Hidden Pages (not_in_nav)

Include documents in the build but exclude them from navigation warnings:

nav:
  - Home: index.md
  - Guide: guide.md

not_in_nav: |
  /internal-reference.md
  /hidden/*.md

🚀 Getting Started

Installation

MkDocs requires Python and pip. Install MkDocs using pip:

pip install mkdocs

For additional themes and plugins:

pip install mkdocs-material  # Popular Material theme

Creating a New Project

mkdocs new my-project
cd my-project

This creates the minimal project structure with mkdocs.yml and docs/index.md.

Development Server

Start the built-in development server:

mkdocs serve

Open http://127.0.0.1:8000/ in your browser. The server supports:

  • Auto-reload: Rebuilds on file changes
  • Live refresh: Browser automatically refreshes
  • URL mapping: Simulates production URL structure

Building the Site

Generate the static site:

mkdocs build

The output is written to the site/ directory, ready for deployment.

Deploying to GitHub Pages

MkDocs includes built-in GitHub Pages deployment:

mkdocs gh-deploy

This command:

  1. Builds the documentation
  2. Commits to the gh-pages branch
  3. Pushes to GitHub

Custom Domains

For custom domains on GitHub Pages, add a CNAME file to your docs/ directory:

docs.example.com

This ensures the CNAME file is included in every deployment.

Alternative Deployment Options

Read the Docs

Read the Docs offers free documentation hosting with MkDocs support out-of-the-box:

  1. Create an account on Read the Docs
  2. Connect your repository
  3. Documentation auto-updates on each push

Local File Distribution

For offline documentation, configure MkDocs for the file:// scheme:

site_url: ""
use_directory_urls: false
plugins: []  # Disable search for offline use

404 Pages

MkDocs automatically generates a 404.html file. GitHub Pages uses this automatically for custom domains. Other hosts may require configuration.

✅ Best Practices

1. Content Organization

  • Logical Structure: Organize content by topic or user journey
  • Navigation: Define clear navigation in mkdocs.yml
  • Index Pages: Create overview pages for each section
  • Cross-References: Use relative links between pages
nav:
  - Home: index.md
  - User Guide:
    - Overview: user-guide/index.md
    - Installation: user-guide/installation.md
    - Configuration: user-guide/configuration.md
  - API Reference:
    - Overview: api/index.md
    - Endpoints: api/endpoints.md

2. Writing Guidelines

YAML Front Matter

Use YAML front matter for page metadata:

---
title: Page Title
description: Brief description for SEO
authors:
  - Author Name
date: 2025-01-01
---

Images

Store images in organized subdirectories:

![Screenshot](img/screenshot.png)

3. Development Workflow

  1. Write: Create/edit Markdown files in docs/
  2. Preview: Use mkdocs serve for local development
  3. Build: Run mkdocs build to generate HTML
  4. Test: Verify the generated site locally
  5. Deploy: Push changes or run mkdocs gh-deploy

4. Version Control Considerations

Add to .gitignore:

site/
.cache/

🚀 Advanced Features

1. Themes and Styling

Built-in Themes

MkDocs includes two built-in themes:

  • mkdocs: Clean, simple default theme
  • readthedocs: Inspired by Read the Docs
theme:
  name: readthedocs

Material for MkDocs

The most popular third-party theme:

pip install mkdocs-material
theme:
  name: material
  palette:
    primary: indigo
    accent: indigo
  features:
    - navigation.tabs
    - navigation.sections
    - search.highlight

Custom CSS

Add custom styling:

extra_css:
  - css/custom.css

2. Markdown Extensions

MkDocs uses Python-Markdown with support for extensions:

markdown_extensions:
  - toc:
      permalink: true
      separator: "_"
  - admonition
  - codehilite:
      guess_lang: false
  - tables
  - fenced_code

Admonitions (with admonition extension)

!!! note
    This is a note admonition.

!!! warning "Custom Title"
    This is a warning with a custom title.

!!! danger
    This is a danger admonition.

Code Highlighting

```python
def hello_world():
    print("Hello, World!")
```

3. Plugins

MkDocs has a rich plugin ecosystem:

plugins:
  - search:
      lang: en
      separator: '[\s\-\.]+'
      min_search_length: 3
      prebuild_index: true
      indexing: full  # or 'sections', 'titles'
  - minify:
      minify_html: true

Conditional Plugin Enabling (MkDocs 1.6+)

Use environment variables to conditionally enable plugins:

plugins:
  - search
  - code-validator:
      enabled: !ENV [LINT, false]

Hooks (Lightweight Plugins)

MkDocs 1.4+ supports hooks for simple customizations without creating full plugins:

hooks:
  - my_hooks.py
# my_hooks.py
def on_page_markdown(markdown, **kwargs):
    return markdown.replace('TODO', '⚠️ TODO')

🔧 Troubleshooting Common Issues

1. Build Errors

Symptom: mkdocs build fails with errors

Solutions:

  • Check mkdocs.yml syntax (YAML is indentation-sensitive)
  • Verify all navigation paths exist
  • Ensure Markdown files are valid

3. Theme Not Found

Symptom: Theme errors during build

Solutions:

  • Install the theme: pip install mkdocs-material
  • Verify theme name in mkdocs.yml
  • Check for typos in theme configuration

4. GitHub Pages Not Updating

Symptom: Changes don’t appear after deployment

Solutions:

  • Clear browser cache
  • Check GitHub Actions logs
  • Verify gh-pages branch exists
  • Wait a few minutes for propagation

📊 Monitoring and Maintenance

2. Build Performance

For large sites, optimize builds:

plugins:
  - search:
      prebuild_index: true
      indexing: sections  # or 'titles' for smaller index

3. Content Updates

  • Regular review of documentation accuracy
  • Update dependencies: pip install --upgrade mkdocs
  • Monitor site performance

🎯 Conclusion

MkDocs provides a powerful yet simple platform for creating professional documentation websites. Its Python-based architecture, combined with a rich plugin ecosystem and excellent theme support, makes it an excellent choice for:

  • Project documentation
  • Technical guides
  • API documentation
  • Knowledge bases

The combination of Markdown simplicity, YAML configuration, and static site generation ensures fast, maintainable documentation that can be hosted anywhere.

📚 References

Official Documentation

MkDocs Official Documentation [📘 Official]

The comprehensive official guide to MkDocs, covering all features from basic usage to advanced configurations. This is the primary resource for understanding MkDocs’ capabilities, syntax, and best practices.

MkDocs Configuration Reference [📘 Official]

Detailed reference for all mkdocs.yml configuration options including validation, plugins, themes, and special YAML tags like !ENV and !relative.

MkDocs Deployment Guide [📘 Official]

Comprehensive guide covering GitHub Pages, Read the Docs, custom hosting, local file distribution, and 404 page configuration.

Themes and Extensions

Material for MkDocs [📘 Official] including extensive customization options, built-in plugins (blog, social cards, search), code annotations, 10,000+ icons, and features like instant loading and dark mode. Trusted by FastAPI, Hummingbot, and many more.

MkDocs Plugin Catalog [📘 Official]

A curated catalog of 300+ MkDocs plugins and themes across 17 categories including theming, API documentation, charts, navigation, PDF export, and more. Essential for discovering extensions.

Python-Markdown Extensions [📘 Official]

Documentation for 18+ officially supported Python-Markdown extensions including admonitions, code highlighting, tables, footnotes, and table of contents. Also links to third-party extensions.

Deployment and Hosting

GitHub Pages Documentation [📘 Official]

GitHub’s official documentation for Pages, explaining site types (project/organization), custom domains, HTTPS, and troubleshooting. Essential for mkdocs gh-deploy usage.

Foundational References

Markdown Guide [📗 Community-Verified]

Comprehensive reference for Markdown syntax and best practices covering basic syntax, extended features, and tool-specific implementations.

YAML Specification [📘 Official]

Official YAML 1.2 specification, essential for understanding the syntax used in mkdocs.yml configuration files including special tags and data types.

📑 APPENDIXES

APPENDIX A: MkDocs Architecture - How MkDocs Works

A deep dive into MkDocs’ core architecture, including the build pipeline, plugin system, and rendering process. This guide explains how MkDocs transforms Markdown into HTML, the role of Jinja2 templates, and the event-driven plugin architecture.

APPENDIX B: MkDocs Architecture - Monolithic vs. Modular Deployment

A comprehensive analysis of deployment strategies for MkDocs sites, covering monolithic builds, incremental deployment options, and multi-site architectures. Essential for understanding when and how to scale MkDocs documentation.

APPENDIX C: Quarto vs MkDocs Comparison

A detailed comparison between Quarto and MkDocs, covering architecture, features, use cases, and trade-offs. This appendix is included at the end of the deployment article to help teams choose the right tool.